{
 "cells": [
  {
   "cell_type": "markdown",
   "id": "c0ba5ed0",
   "metadata": {},
   "source": [
    "## 一、python文档\n",
    "\n",
    "这部分涉及python的一些基础的知识点辨析。\n",
    "\n",
    "### 二、操作及运算符\n",
    "\n",
    "#### 2.1 比较is与“==”\n",
    "1) \"is\"是一个**关键字**用于判断两个对象是否为同一个对象（比较内存地址）\n",
    "2) \"==\"则用来判断两个对象的值是否相同。\n",
    "\n",
    "### 三、python中的关键字\n",
    "\n",
    "在 Python 中，关键字是具有特殊意义的保留字，不能用作变量、函数或标识符的名称。python中关键字主要分布在下面领域中：布尔值、逻辑运算、程序控制结构（流程控制和循环控制）、异常处理、函数声明关键字、作用域、导入及模块处理、上下文管理。\n",
    "\n",
    "#### 3.1 yield：生成器\n",
    "（1）示例程序1：函数内部多个yield语句，依次进行返回\n",
    "    如何清除生成器对应记录的值？让它重新开始记录（重置状态）？\n",
    "    a. 生成一个新的生成器对象\n",
    "    b. 调用生成器对象的关闭函数gen.close()\n",
    "    c. 自定义类中实现对应的逻辑\n",
    "（2）示例程序2：函数内部根据执行逻辑，按需调用 并返回对应的值\n",
    "\n",
    "### 四、文件读取操作\n",
    "\n",
    "#### 4.1 read() readline() readlines() 这三者之间有什么区别和联系？\n",
    "read读取整个文件，返回一个字符串；readline读取每一行，将每一行作为一个字符串来返回。\n",
    "关于文件读取操作，open函数的其它参数的使用。\n",
    "\n",
    "### 五、类的继承和面向对象的编程\n",
    "\n",
    "#### 5.1什么是python面向对象的继承特点？\n",
    "使用super()函数可以无须显式地指定父类名称而调用父类的方法。这在多重继承中尤为有效。（为什么？）\n",
    "\n",
    "\n",
    "### 六、python的内置函数\n",
    "\n",
    "#### 6.1 python中any()和all()有什么作用？\n",
    "\n",
    "#### 6.2 enumerate的用法\n",
    "\n",
    "（1）enumerate和zip函数一起使用的效果\n",
    "\n",
    "\n",
    "\n",
    "### 七、python3中的装饰器\n",
    "\n",
    "1) 什么是装饰器，它的定义是什么？\n",
    "2) 如何使用装饰器？请举例说明\n",
    "3) 带参数的装饰器，如何使用？请举例说明……\n",
    "装饰器可以用于日志处理、性能测试、缓存和权限校验等领域。可应用于函数、方法或类。\n",
    "\n",
    "\n",
    "### 附录\n",
    "1. [python官方文档](https://wiki.python.org/moin/BeginnersGuideChinese)\n",
    "2. [面向对象：类的定义及使用](https://www.runoob.com/python3/python3-class.html)\n",
    "3. [子类继承父类：构造函数说明](https://www.runoob.com/w3cnote/python-extends-init.html)\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 1,
   "id": "9ceb37b6",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "True\n",
      "True\n",
      "False\n",
      "True\n"
     ]
    }
   ],
   "source": [
    "#### 2.1 比较is与“==”\n",
    "\n",
    "a = [1,2,3]\n",
    "b = a\n",
    "c = b\n",
    "d = [1,2,3]\n",
    "\n",
    "print(b is a)\n",
    "print(c is a) # 这里is判断用来判断“c”和“a”是否指向同一块内存地址（对象）\n",
    "print(d is a)\n",
    "\n",
    "print(d == a) # 判断两个对象地址的内容（值）是否相同。\n",
    "\n",
    "## ====================================================\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "id": "673fbc6b",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "['False', 'None', 'True', 'and', 'as', 'assert', 'async', 'await', 'break', 'class', 'continue', 'def', 'del', 'elif', 'else', 'except', 'finally', 'for', 'from', 'global', 'if', 'import', 'in', 'is', 'lambda', 'nonlocal', 'not', 'or', 'pass', 'raise', 'return', 'try', 'while', 'with', 'yield']\n",
      "Python关键字总数: 35\n"
     ]
    }
   ],
   "source": [
    "#### 三、python中的关键字\n",
    "import keyword\n",
    "print(keyword.kwlist) # 打印Python关键字列表\n",
    "print(f\"Python关键字总数: {len(keyword.kwlist)}\") # 统计关键字数量"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "id": "9a9e2d5a",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "hello,I am a student.\n",
      "what about you?\n",
      "Can you tell me?\n",
      "Here is my email:xxxxxxxxx\n",
      "And how can we human studying python work and life?\n",
      "I think if life is a poem and I must be a poet\n",
      "\n",
      "omga, this file is a test that I used to study file exercise\n",
      "OK,that's OK\n",
      "END\n",
      "========================================================\n",
      "hello,I am a student.\n",
      "what about you?\n",
      "Can you tell me?\n",
      "Here is my email:xxxxxxxxx\n",
      "And how can we human studying python work and life?\n",
      "I think if life is a poem and I must be a poet\n",
      "\n",
      "omga, this file is a test that I used to study file exercise\n",
      "OK,that's OK\n",
      "END\n",
      "========================================================\n",
      "hello,I am a student.\n",
      "what about you?\n",
      "Can you tell me?\n",
      "Here is my email:xxxxxxxxx\n",
      "And how can we human studying python work and life?\n",
      "I think if life is a poem and I must be a poet\n",
      "\n",
      "omga, this file is a test that I used to study file exercise\n",
      "OK,that's OK\n",
      "END\n"
     ]
    }
   ],
   "source": [
    "#### 4.1 read() readline() readlines() 这三者之间有什么区别和联系？\n",
    "END_STRING = '========================================================'  #在两个不同的输出结果中间打印分隔符\n",
    "\n",
    "with open('test.text','r') as f:\n",
    "    content = f.read()              #read()\n",
    "    print(content)\n",
    "\n",
    "\n",
    "print(END_STRING)\n",
    "\n",
    "with open('test.text','r') as f:\n",
    "    fline = f.readline()            #readline()\n",
    "    while fline:\n",
    "        print(fline.strip())  ##如果写为fline,那么每一行结束后都会打印出一个换行符。\n",
    "        fline = f.readline()\n",
    "\n",
    "print(END_STRING)\n",
    "\n",
    "with open('test.text','r') as f:\n",
    "    lines = f.readlines()\n",
    "\n",
    "    for line in lines:\n",
    "        print(line.strip())  ## 每一行输出之间相隔两行？挺奇怪的\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "id": "cb799b28",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Hello from Base\n",
      "Hello from Sub\n"
     ]
    }
   ],
   "source": [
    "#### 5.1什么是python面向对象的继承特点？\n",
    "\n",
    "\n",
    "class Base:\n",
    "    def greet(self):\n",
    "        print(\"Hello from Base\")\n",
    "\n",
    "class Sub(Base):\n",
    "    def greet(self):\n",
    "        super().greet()\n",
    "        print(\"Hello from Sub\")\n",
    "\n",
    "obj = Sub()\n",
    "obj.greet()  # 输出：Hello from Base\\nHello from Sub\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "id": "e8ad73fe",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "True\n",
      "True\n",
      "True\n",
      "True\n",
      "False\n"
     ]
    }
   ],
   "source": [
    "#### 6.1 python中any()和all()有什么作用？\n",
    "a = [1,False,False,False]\n",
    "a2 = []\n",
    "b = [True,1,2,3]\n",
    "b2 = [True,1,2,False]\n",
    "print(any(a))\n",
    "print(any(a))\n",
    "# print(END_STRING)\n",
    "print(all(a2))\n",
    "print(all(b))\n",
    "print(all(b2))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "id": "7ef029dd",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Something is happening before the function is called.\n",
      "My say_hello !\n",
      "Something is happening after the function is called.\n"
     ]
    }
   ],
   "source": [
    "### 七、python3中的装饰器\n",
    "\n",
    "def my_decorator(func):\n",
    "    def wrapper():\n",
    "        print(\"Something is happening before the function is called.\")\n",
    "        func()\n",
    "        print(\"Something is happening after the function is called.\")\n",
    "    return wrapper\n",
    "\n",
    "# @my_decorator\n",
    "# def say_hello():\n",
    "#     print(\"Hello!\")\n",
    "\n",
    "# say_hello()\n",
    "\n",
    "def say_hello():\n",
    "    print(\"My say_hello !\")    \n",
    "\n",
    "say_hello = my_decorator(say_hello)             ## 等价于使用装饰器@my_decorator\n",
    "                                                ##              def say_hello():\n",
    "say_hello()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "id": "c321666d",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Hello World!\n",
      "Hello World!\n",
      "Hello World!\n"
     ]
    }
   ],
   "source": [
    "#### 3) 带参数的装饰器\n",
    "def repeat(num_times):\n",
    "    def decorator(func):\n",
    "        def wrapper(*args, **kwargs):\n",
    "            for _ in range(num_times):\n",
    "                func(*args, **kwargs)\n",
    "        return wrapper\n",
    "    return decorator\n",
    "\n",
    "@repeat(3)\n",
    "def greet(name):\n",
    "    print(f\"Hello {name}!\")\n",
    "\n",
    "greet(\"World\")\n"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "ed3dee0b",
   "metadata": {},
   "source": [
    "下面为你详细解释这些疑问，帮助你理解带参数装饰器中参数传递和函数调用的机制。\n",
    "\n",
    "### 为什么 `func` 是被装饰的函数\n",
    "在Python装饰器的机制里，装饰器本质上是一个函数，它接收一个函数作为输入，然后返回一个新的函数。在这个带参数的装饰器例子中，`repeat` 函数的作用是生成一个装饰器，而 `decorator` 函数才是真正用来装饰其他函数的装饰器。\n",
    "\n",
    "当你使用 `@repeat(3)` 语法糖装饰 `greet` 函数时，Python解释器会将其转换为 `greet = repeat(3)(greet)`。具体执行步骤如下：\n",
    "1. `repeat(3)` 被调用，它返回 `decorator` 函数。此时 `num_times` 的值被固定为 3。\n",
    "2. `repeat(3)(greet)` 等价于 `decorator(greet)`，这里 `greet` 函数作为参数传递给 `decorator` 函数，所以在 `decorator` 函数内部，`func` 就是被装饰的函数 `greet`。\n",
    "\n",
    "### Python解释器如何辨认是 `func` 参数而不是 `num_times`\n",
    "Python解释器是根据函数调用时的参数传递顺序和上下文来辨认参数的。在 `repeat(3)(greet)` 这个调用过程中：\n",
    "- `repeat(3)` 调用时，3 作为参数传递给 `repeat` 函数的 `num_times` 参数。\n",
    "- `repeat(3)` 返回 `decorator` 函数后，接着调用 `decorator(greet)`，此时 `greet` 函数作为参数传递给 `decorator` 函数的 `func` 参数。\n",
    "\n",
    "### `func` 在函数内部传入是怎么实现的\n",
    "`func` 并不是在 `repeat` 函数内部传入的，而是在 `decorator` 函数被调用时传入的。整个过程是分步骤完成的：\n",
    "1. **定义装饰器生成函数 `repeat`**：它接收一个参数 `num_times`，用于指定被装饰函数要重复执行的次数。`repeat` 函数返回 `decorator` 函数。\n",
    "2. **使用装饰器生成装饰器实例**：`repeat(3)` 调用后，返回一个基于 `num_times` 为 3 的 `decorator` 函数实例。\n",
    "3. **装饰函数**：`decorator(greet)` 调用时，`greet` 函数作为参数传递给 `decorator` 函数，`decorator` 函数内部的 `func` 就指向了 `greet` 函数。\n",
    "4. **返回包装函数**：`decorator` 函数返回 `wrapper` 函数，这个 `wrapper` 函数会在调用时执行 `func` 函数（即 `greet` 函数）指定的次数。\n",
    "\n",
    "以下是添加了一些打印语句的代码，帮助你更清晰地看到参数传递和函数调用的过程：\n",
    "```python\n",
    "def repeat(num_times):\n",
    "    print(f\"repeat 函数被调用，num_times = {num_times}\")\n",
    "\n",
    "    def decorator(func):\n",
    "        print(f\"decorator 函数被调用，func = {func.__name__}\")\n",
    "\n",
    "        def wrapper(*args, **kwargs):\n",
    "            print(\"wrapper 函数被调用\")\n",
    "            for _ in range(num_times):\n",
    "                func(*args, **kwargs)\n",
    "        return wrapper\n",
    "    return decorator\n",
    "\n",
    "@repeat(3)\n",
    "def greet(name):\n",
    "    print(f\"Hello {name}!\")\n",
    "\n",
    "print(\"开始调用 greet 函数\")\n",
    "greet(\"World\")\n",
    "\n",
    "```\n",
    "运行上述代码，你可以看到不同函数的调用顺序和参数传递情况，从而更好地理解整个过程。 "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "id": "ee218696",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "repeat 函数被调用，num_times = 3\n",
      "decorator 函数被调用，func = greet\n",
      "开始调用 greet 函数\n",
      "wrapper 函数被调用\n",
      "Hello World!\n",
      "Hello World!\n",
      "Hello World!\n"
     ]
    }
   ],
   "source": [
    "def repeat(num_times):\n",
    "    print(f\"repeat 函数被调用，num_times = {num_times}\")\n",
    "\n",
    "    def decorator(func):\n",
    "        print(f\"decorator 函数被调用，func = {func.__name__}\")\n",
    "\n",
    "        def wrapper(*args, **kwargs):\n",
    "            print(\"wrapper 函数被调用\")\n",
    "            for _ in range(num_times):\n",
    "                func(*args, **kwargs)\n",
    "        return wrapper\n",
    "    return decorator\n",
    "\n",
    "@repeat(3)\n",
    "def greet(name):\n",
    "    print(f\"Hello {name}!\")\n",
    "\n",
    "print(\"开始调用 greet 函数\")\n",
    "greet(\"World\")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "id": "e2703aaa",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Added by decorator\n"
     ]
    }
   ],
   "source": [
    "### 类装饰器\n",
    "def class_decorator(cls):\n",
    "    cls.class_attr = 'Added by decorator'\n",
    "    return cls\n",
    "\n",
    "@class_decorator\n",
    "class MyClass:\n",
    "    pass\n",
    "\n",
    "print(MyClass.class_attr)  # 输出 'Added by decorator'\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "c135de9a",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "1\n",
      "2\n",
      "1\n",
      "2\n",
      "3\n",
      "4\n"
     ]
    }
   ],
   "source": [
    "#### 3.1 yield：生成器\n",
    "## （1）示例程序1：函数内部多个yield语句，依次进行返回\n",
    "def sample_yield():\n",
    "    yield 1\n",
    "    yield 2\n",
    "    yield 3\n",
    "    yield 4\n",
    "\n",
    "# print(sample_yield())   #返回一个生成器函数，如果直接打印，则显示一个内存地址：<generator object sample_yield at 0x000001848815F740>\n",
    "\n",
    "generate = sample_yield()\n",
    "print(next(generate))   # 1\n",
    "print(next(generate))   #2\n",
    "generate.close()\n",
    "\n",
    "\n",
    "# for _ in range(5):  \n",
    "#     print(next(generate))   \n",
    "\n",
    "generate = sample_yield()\n",
    "for _ in range(4):\n",
    "    print(next(generate))\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 18,
   "id": "da94c53b",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "0\n",
      "1\n",
      "1\n",
      "2\n",
      "3\n",
      "5\n",
      "8\n",
      "13\n",
      "21\n",
      "34\n",
      "55\n"
     ]
    }
   ],
   "source": [
    "## （2）示例程序2：函数内部根据执行逻辑，按需调用 并返回对应的值\n",
    "\n",
    "def fibonacci():\n",
    "    a,b = 0,1\n",
    "    while True:\n",
    "        yield a\n",
    "        a,b = b,a+b\n",
    "\n",
    "gen = fibonacci()\n",
    "print(next(gen))\n",
    "\n",
    "for _ in range(10):\n",
    "    print(next(gen))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "2b71f572",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "0 0\n",
      "1 2\n",
      "2 4\n",
      "3 6\n",
      "4 8\n",
      "5 10\n",
      "========================================================\n",
      "1 0\n",
      "2 2\n",
      "3 4\n",
      "4 6\n",
      "5 8\n",
      "6 10\n"
     ]
    }
   ],
   "source": [
    "#### 6.2 enumerate的用法\n",
    "list_sample = [0,2,4,6,8,10]\n",
    "for index,data in enumerate(list_sample):\n",
    "    print(index,data)\n",
    "print(END_STRING)\n",
    "for index,data in enumerate(list_sample,start=1):   #指定起始索引\n",
    "    print(index,data)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "a5a0492d",
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "0 2 3\n",
      "1 4 6\n",
      "2 6 9\n",
      "3 8 12\n",
      "4 10 15\n"
     ]
    }
   ],
   "source": [
    "\n",
    "item1 = [2,4,6,8,10]\n",
    "item2 = [3,6,9,12,15]\n",
    "for index,(item1,item2) in enumerate(zip(item1,item2)):\n",
    "    print(index,item1,item2)"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "env_py38",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.8.18"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
